﻿// Copyright (C) 2014 Can Batu Erdem
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with this program.  If not, see <http://www.gnu.org/licenses/>.

using Cyrene.Strategy;
using System;
using System.Collections.Specialized;
using System.Text;
using System.Web;


namespace Cyrene.Serializer
{
    internal static class HttpContextSerializer
    {
        internal static string Serialize(TableGeneratorStrategy tableGenerator, HttpContext httpContext)
        {
            if (httpContext == null)
            {
                throw new ArgumentNullException("httpContext");
            }

            StringBuilder sb = new StringBuilder();

            NameValueCollection httpContextCollection = new NameValueCollection();
            httpContextCollection.Add("Url", httpContext.Request.RawUrl);
            httpContextCollection.Add("Server Name", httpContext.Server.MachineName);
            httpContextCollection.Add("Logon User", httpContext.User.Identity.Name);
            httpContextCollection.Add("Client IP", httpContext.Request.UserHostAddress);
            httpContextCollection.Add("Client Browser", string.Format("{0} ({1})", httpContext.Request.Browser.Browser, httpContext.Request.Browser.Version));
            httpContextCollection.Add("Previous Page", httpContext.Request.UrlReferrer != null ? httpContext.Request.UrlReferrer.ToString() : string.Empty);
            sb.Append(tableGenerator.Generate("HttpContext Summary", httpContextCollection));

            if (httpContext.Request.QueryString.Count > 0)
            {
                sb.Append(tableGenerator.Generate("Query String", httpContext.Request.QueryString));
            }

            if (httpContext.Request.Form.Count > 0)
            {
                sb.Append(tableGenerator.Generate("Form", httpContext.Request.Form));
            }

            if (httpContext.Request.Cookies.Count > 0)
            {
                sb.Append(SerializeCookies(tableGenerator, httpContext.Request.Cookies));
            }

            if (httpContext.Session.Count > 0)
            {
                sb.Append(SerializeSession(tableGenerator, httpContext.Session));
            }

            if (httpContext.Request.ServerVariables.Count > 0)
            {
                sb.Append(tableGenerator.Generate("Server Variables", httpContext.Request.ServerVariables));
            }

            return sb.ToString();
        }

        private static string SerializeCookies(TableGeneratorStrategy tableGenerator, HttpCookieCollection httpCookieCollection)
        {
            NameValueCollection nameValueCollection = new NameValueCollection();
            try
            {
                foreach (string str in httpCookieCollection.Keys)
                {
                    nameValueCollection.Add(str, httpCookieCollection[str].Value);
                }
            }
            catch (Exception ex)
            {
                nameValueCollection.Add("Error", ex.Message);
            }
            return (nameValueCollection.Count > 0) ? tableGenerator.Generate("Cookies", nameValueCollection) : string.Empty;
        }

        private static string SerializeSession(TableGeneratorStrategy tableGenerator, System.Web.SessionState.HttpSessionState httpSessionState)
        {
            NameValueCollection nameValueCollection = new NameValueCollection();

            try
            {
                nameValueCollection.Add("IsNewSession", httpSessionState.IsNewSession.ToString());
                nameValueCollection.Add("SessionID", httpSessionState.SessionID);
                foreach (string str in httpSessionState.Keys)
                {
                    nameValueCollection.Add(str, httpSessionState[str] == null ? string.Empty : httpSessionState[str].ToString());
                }
            }
            catch (Exception ex)
            {
                nameValueCollection.Add("Error", ex.Message);
            }

            return tableGenerator.Generate("Session", nameValueCollection);
        }
    }
}
